from django.http import HttpResponse, JsonResponse
from django.shortcuts import render, redirect
from django.template import loader

from django.views import View
from pyecharts.charts import Map, Line, Bar, Pie
from pyecharts.commons.utils import JsCode
from pyecharts.faker import Faker

# from . import Get_data
# from .selenium_get import SeleniumGet
from visual.models import ProjectData, CityData, DangerousAreas, IntegratedData
from pyecharts import options as opts


def city_pie(city):
    results = CityData.objects.filter(area=city).values('city', "confirmed")  # 获取每个城市累计确诊的值
    cityList = []
    confirmedList = []
    for item in results:
        cityList.append(item['city'])
        confirmedList.append(item["confirmed"])

    data_pair = [list(z) for z in zip(cityList, confirmedList)]
    data_pair.sort(key=lambda x: x[1])
    # print(cityList)
    # print(confirmedList)
    pie = Pie(init_opts=opts.InitOpts(width="570px", height="700px"))
    pie.add('累计确诊', data_pair,
            center=["50%", "60%"], label_opts=opts.LabelOpts(is_show=False, position="center"), )
    pie.set_global_opts(title_opts=opts.TitleOpts(title=city+"各地累计确诊"),
                        legend_opts=opts.LegendOpts(pos_top="50px"), )
    # 标签名称显示，默认为True
    pie.set_series_opts(label_opts=opts.LabelOpts(position="left",
                                                  formatter="{b}: {c}"))  # label_opts=opts.LabelOpts(formatter="{b}: {c}") 字典形式显示
    return pie


def city_map(city):
    try:
        results = CityData.objects.filter(area=city).values('city', 'curConfirm')
        # print(results)
        visual_data = []
        for item in results:
            visual_data.append([item['city'], item['curConfirm']])
        c = Map(init_opts=opts.InitOpts(width="400px", height="600px"))
        c.add("现有确诊", visual_data, city)
        c.set_global_opts(
            title_opts=opts.TitleOpts(title=city + "地图"), visualmap_opts=opts.VisualMapOpts()
        )
        return c
    except:
        return china_map()


def city_line(city):
    city_line = Line(init_opts=opts.InitOpts(width="500px", height="350px"))  # animation_opts 动画延迟
    result = CityData.objects.filter(area=city).values('city', 'cured', 'died', "confirmed")
    # print(result)
    city = []
    cured = []
    died = []
    confirmed = []
    for item in result:
        city.append(item['city'])
        cured.append(int(item['cured']))
        if item['died'] == '':
            died.append(0)
        else:
            died.append(int(item['died']))
        confirmed.append(item['confirmed'])
    cured_rate = []
    death_rate = []
    # 获取治愈率  死亡率
    for item in range(len(confirmed)):
        if confirmed[item] == 0:
            death_rate.append(0)
            cured_rate.append(1)
        elif died[item] == 0:
            death_rate.append(0)
            cured_rate.append(float(cured[item] / confirmed[item]))

        elif cured[item] == 0:
            death_rate.append(float(died[item] / confirmed[item]))
            cured_rate.append(0)
        else:
            death_rate.append(float(died[item] / confirmed[item]))
            cured_rate.append(float(cured[item] / confirmed[item]))
    # print(cured_rate, death_rate, city)
    city_line.add_xaxis(xaxis_data=city)
    # areastyle_opts=opts.AreaStyleOpts(opacity=0.5) 曲线下的面积
    city_line.add_yaxis("死亡率", death_rate, is_smooth=True, areastyle_opts=opts.AreaStyleOpts(opacity=0.2))  # 曲线
    city_line.add_yaxis("治愈率", cured_rate,
                        itemstyle_opts=opts.ItemStyleOpts(color="rgb(20,20,215)"))  # ,is_selected=False 设置默认初始不显示
    city_line.set_series_opts(
        # 标签名称显示，默认为True
        label_opts=opts.LabelOpts(is_show=False, color="blue"),

    )
    city_line.set_global_opts(
        #  设置操作图表缩放功能，orient="vertical" 为Y轴 滑动
        datazoom_opts=opts.DataZoomOpts(),  # 实现数据平移
        title_opts=opts.TitleOpts(title="地区情况"),  # 标题, # 副标题 subtitle="死亡率和治愈率"
        legend_opts=opts.LegendOpts(is_show=True),  # 顶标显示
        yaxis_opts=opts.AxisOpts(name="死亡/治愈率"),  # X轴的名称
        xaxis_opts=opts.AxisOpts(name="市区"),
    )
    return city_line


def city_bar(city):
    citybar = Bar(init_opts=opts.InitOpts(width="500px", height="350px"))
    results = CityData.objects.filter(area=city).values('city', 'cured', 'died')
    area = []
    cured = []
    died = []
    for item in results:
        area.append(item['city'])
        cured.append(int(item['cured']))
        if item['died'] == '':
            died.append(0)
        else:
            died.append(int(item['died']))
    citybar.add_xaxis(area)
    citybar.add_yaxis('累计死亡', died)
    citybar.add_yaxis('累计治愈', cured)  # category_gap=0间隔为0
    # .add_yaxis('累计死亡', [int(i) for i in df['died'].values], stack="stack1")  # stack="stack1" 堆积柱状图
    citybar.set_series_opts(
        # 标签名称显示，默认为True
        label_opts=opts.LabelOpts(is_show=False, color="blue"),
        markline_opts=opts.MarkLineOpts(
            data=[
                opts.MarkLineItem(type_="min", name="最小值"),
                opts.MarkLineItem(type_="average", name="平均值"),
                # opts.MarkLineItem(y=20000, name="yAxis=10")
            ]),  # Y轴设置一条线
        markpoint_opts=opts.MarkPointOpts(
            data=[
                opts.MarkPointItem(type_="max", name='最大值')
            ]),
    )

    citybar.set_global_opts(
        # xaxis_opts=opts.AxisOpts(axisline_opts=opts.AxisLineOpts(linestyle_opts=opts.LineStyleOpts())),
        #  设置操作图表缩放功能，orient="vertical" 为Y轴 滑动
        datazoom_opts=opts.DataZoomOpts(),
    )
    return citybar


def china_map():
    result = ProjectData.objects.all().values('area', 'curConfirm')
    curConfirm_data = []
    for item in result:
        curConfirm_data.append([item['area'], item['curConfirm']])
    # print(visual_data)
    china_map = Map(init_opts=opts.InitOpts(width="550px", height="650px", chart_id='chart_111'))
    china_map.add("现有确诊", curConfirm_data, 'china')
    china_map.set_global_opts(
        visualmap_opts=opts.VisualMapOpts(max_=3000, is_piecewise=True),
        title_opts=opts.TitleOpts(title="COVID-19国内疫情数据")
    )
    china_map.set_series_opts(
        # 标签名称显示，默认为True
        label_opts=opts.LabelOpts(is_show=False, color="blue")
    )
    return china_map


def line():
    line = Line(init_opts=opts.InitOpts(width="400px", height="300px", animation_opts=opts.AnimationOpts(
        animation_delay=1000, animation_easing="elasticOut"
    )))  # animation_opts 动画延迟
    result = ProjectData.objects.all().values('area', 'crued', 'died', "confirmed")
    area = []
    cured = []
    died = []
    confirmed = []
    for item in result:
        area.append(item['area'])
        cured.append(int(item['crued']))
        died.append(int(item['died']))
        confirmed.append(item['confirmed'])
    cured_rate = []
    death_rate = []
    # 获取治愈率  死亡率
    for item in range(len(confirmed)):
        death_rate.append(float(died[item] / confirmed[item]))
        cured_rate.append(float(cured[item] / confirmed[item]))
    line.add_xaxis(xaxis_data=area)
    # areastyle_opts=opts.AreaStyleOpts(opacity=0.5) 曲线下的面积
    line.add_yaxis("死亡率", death_rate, is_smooth=True, areastyle_opts=opts.AreaStyleOpts(opacity=0.2))  # 曲线
    line.add_yaxis("治愈率", cured_rate,
                   itemstyle_opts=opts.ItemStyleOpts(color="rgb(20,20,215)"))  # ,is_selected=False 设置默认初始不显示
    line.set_series_opts(
        # 标签名称显示，默认为True
        label_opts=opts.LabelOpts(is_show=False, color="blue"),

    )
    line.set_global_opts(
        #  设置操作图表缩放功能，orient="vertical" 为Y轴 滑动
        datazoom_opts=opts.DataZoomOpts(),  # 实现数据平移
        # toolbox_opts=opts.ToolboxOpts(),  # 显示工具框
        title_opts=opts.TitleOpts(title="地区情况"),  # 标题, # 副标题 subtitle="死亡率和治愈率"
        legend_opts=opts.LegendOpts(is_show=True),  # 顶标显示
        yaxis_opts=opts.AxisOpts(name="死亡/治愈率"),  # X轴的名称
        xaxis_opts=opts.AxisOpts(name="省份"),
        graphic_opts=[  # 设置一个标签
            opts.GraphicGroup(
                graphic_item=opts.GraphicItem(
                    rotation=JsCode("Math.PI / 4"),
                    bounding="raw",
                    right=110,
                    bottom=110,
                    z=100,
                ),
                children=[
                    opts.GraphicRect(
                        graphic_item=opts.GraphicItem(
                            left="center", top="center", z=100
                        ),
                        graphic_shape_opts=opts.GraphicShapeOpts(width=400, height=50),
                        graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                            fill="rgba(0,0,0,0.3)"
                        ),
                    ),
                    opts.GraphicText(
                        graphic_item=opts.GraphicItem(
                            left="center", top="center", z=100
                        ),
                        graphic_textstyle_opts=opts.GraphicTextStyleOpts(
                            text="COVID-19--Visual",
                            font="bold 26px Microsoft YaHei",
                            graphic_basicstyle_opts=opts.GraphicBasicStyleOpts(
                                fill="#fff"
                            ),
                        ),
                    ),
                ],
            )
        ],
    )
    return line


def bar_data():
    Bar_data = Bar(init_opts=opts.InitOpts(width="480px", height="300px", animation_opts=opts.AnimationOpts(
        animation_delay=1000, animation_easing="elasticOut"
    )))
    results = ProjectData.objects.all().values('area', 'crued', 'died')
    area = []
    cured = []
    died = []
    for item in results:
        area.append(item['area'])
        cured.append(int(item['crued']))
        died.append(int(item['died']))
    Bar_data.add_xaxis(area)
    Bar_data.add_yaxis('累计死亡', died)
    Bar_data.add_yaxis('累计治愈', cured)  # category_gap=0间隔为0
    # .add_yaxis('累计死亡', [int(i) for i in df['died'].values], stack="stack1")  # stack="stack1" 堆积柱状图
    Bar_data.set_series_opts(
        # 标签名称显示，默认为True
        label_opts=opts.LabelOpts(is_show=False, color="blue"),
        markline_opts=opts.MarkLineOpts(
            data=[
                opts.MarkLineItem(type_="min", name="最小值"),
                opts.MarkLineItem(type_="average", name="平均值"),
                # opts.MarkLineItem(y=20000, name="yAxis=10")
            ]),  # Y轴设置一条线
        markpoint_opts=opts.MarkPointOpts(
            data=[
                opts.MarkPointItem(type_="max", name='最大值')
            ]),
    )

    Bar_data.set_global_opts(
        # xaxis_opts=opts.AxisOpts(axisline_opts=opts.AxisLineOpts(linestyle_opts=opts.LineStyleOpts())),
        #  设置操作图表缩放功能，orient="vertical" 为Y轴 滑动
        datazoom_opts=opts.DataZoomOpts(),
    )
    return Bar_data


class Visual(View):
    # Get_data
    # SeleniumGet
    def get(self, request):
        city = request.GET.get('area')
        integrated_data = IntegratedData.objects.all().values()
        DangerousAreaList = DangerousAreas.objects.all().values()
        # print(city)
        try:
            if city:
                city_data = ProjectData.objects.filter(area=city).values('confirmed', 'curConfirm', 'confirmedRelative')
                login = request.session['user']
                if login:
                    c_map = city_map(city)
                    c_line = city_line(city)
                    c_bar = city_bar(city)
                    c_pie = city_pie(city)
                    template = loader.get_template('visual.html')
                    context = dict(
                        CityLine=c_line.render_embed(),
                        CityMap=c_map.render_embed(),
                        CityBar=c_bar.render_embed(),
                        CityPie=c_pie.render_embed(),
                        sign='city',
                        area=city,
                        CityData=city_data,
                        login='true',
                    )
                    # print(city)
                    return HttpResponse(template.render(context, request))
                # else:
                #     c_map = city_map(city)
                #     c_line = city_line(city)
                #     template = loader.get_template('visual.html')
                #     context = dict(
                #         CityMap=c_map.render_embed(),
                #         CityLine=c_line.render_embed(),
                #         area=city,
                #         sign='city',
                #     )
                #     # print(city)
                #     return HttpResponse(template.render(context, request))
            else:
                login = request.session['user']
                if login is not None:
                    template = loader.get_template('visual.html')
                    map = china_map()
                    l = line()
                    bar = bar_data()
                    context = dict(
                        bar=bar.render_embed(),
                        line=l.render_embed(),  # 必须要有
                        map=map.render_embed(),
                        DangerousAreaList=DangerousAreaList,
                        sign='china',
                        integrated_data=integrated_data,
                        login='true'
                    )
                    return HttpResponse(template.render(context, request))
        except:
            if city:
                city_data = ProjectData.objects.filter(area=city).values('confirmed', 'curConfirm', 'confirmedRelative')
                c_map = city_map(city)
                c_line = city_line(city)
                c_bar = city_bar(city)
                c_pie = city_pie(city)
                template = loader.get_template('visual.html')
                context = dict(
                    CityLine=c_line.render_embed(),
                    CityMap=c_map.render_embed(),
                    CityBar=c_bar.render_embed(),
                    CityPie=c_pie.render_embed(),
                    CityData=city_data,
                    sign='city',
                )
                # print(city)
                return HttpResponse(template.render(context, request))
            else:
                template = loader.get_template('visual.html')
                map = china_map()
                l = line()
                bar = bar_data()
                context = dict(
                    line=l.render_embed(),  # 必须要有
                    map=map.render_embed(),
                    bar=bar.render_embed(),
                    integrated_data=integrated_data,
                    DangerousAreaList=DangerousAreaList,
                    sign='china',

                )
                return HttpResponse(template.render(context, request))
